/***************************************************************************
 *  Filename: remotecomputer.cpp
 *  Class: RemoteComputer
 *
 *  Copyright 2012  Xander van Kooten
 *  <xandervk@gmail.com>
 *
 *  Copyright 2012  Mario Henrique Voorsluys
 *  <forcaeluz@gmail.com>
 *
 ****************************************************************************/

/*
 *
 * This file is part of Parsax-Remote-Controller.
 *
 *    Parsax-Remote-Controller is free software: you can redistribute it
 *    and/or modify it under the terms of the GNU General Public License
 *    as published by the Free Software Foundation, either version 3 of the
 *    License, or (at your option) any later version.
 *
 *    Parsax-Remote-Controller is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *    GNU General Public License for more details.
 *
 *    You should have received a copy of the GNU General Public License
 *    along with Parsax-Remote-Controller.
 *    If not, see <http://www.gnu.org/licenses/>.
 */

#include "remotecomputer.h"

RemoteComputer::RemoteComputer(QObject *parent) :
    QObject(parent)
{

    connect(&communicationHandler, SIGNAL(messageReceived(QString)), &parser, SLOT(handleMessage(QString)));
    connect(&communicationHandler, SIGNAL(connectionEstablished()), SLOT(whenConnected()));
    connect(&communicationHandler, SIGNAL(connectionEstablished()), SIGNAL(connectionEstablished()));
    connect(&communicationHandler, SIGNAL(connectionLost()), SLOT(whenDisconnected()));
    connect(&communicationHandler, SIGNAL(connectionLost()), SIGNAL(connectionLost()));
    connect(&parser, SIGNAL(cloReceived(QString,int,QString)), SLOT(whenCLOReceived(QString,int,QString)));
    connect(&parser, SIGNAL(statusReceived(QString,QString)), SLOT(whenStatusUpdateReceived(QString,QString)));
}

void RemoteComputer::setName(QString tname){
    name = tname;
    foreach(RemoteProcess *tmp, processes){
        tmp->setPc(tname);
    }
}

void RemoteComputer::setAddress(QString taddress){
    address = taddress;
}

void RemoteComputer::setPort(int tport){
    port = tport;
}

QString RemoteComputer::getName(){
    return name;
}

QString RemoteComputer::getAddress(){
    return address;
}

int RemoteComputer::getPort(){
    return port;
}

void RemoteComputer::addProccess(){
    addProccess("prg", "noprogram", QStringList(), 0);
}

void RemoteComputer::addProccess(QString id, QString program, QStringList parameters, int timeout){
    Q_UNUSED(timeout);
    RemoteProcess *newProc = new RemoteProcess(this);
    newProc->setId(id);
    newProc->setProgram(program);
    newProc->setParameters(parameters);
    addProccess(newProc);
}

void RemoteComputer::addProccess(RemoteProcess *newProc){
    processes.insert(newProc->getId(), newProc);
    newProc->setPc(getName());
    connect(newProc, SIGNAL(startMe(QString)), SLOT(whenProcessShouldStart(QString)));
    connect(newProc, SIGNAL(stopMe(QString)), SLOT(whenProcessShouldStop(QString)));
}

void RemoteComputer::connectToSlave(){
    communicationHandler.connectToSlave(address, port);
}

void RemoteComputer::disconnectFromSlave(){
    communicationHandler.closeConnection();
}

bool RemoteComputer::isConnected(){
    return communicationHandler.isConnected();
}

void RemoteComputer::whenDisconnected(){
    foreach(RemoteProcess *prcs, processes){
        prcs->setStatus("disconnected");
    }
}

void RemoteComputer::whenConnected(){
    foreach(RemoteProcess *prcs, processes){
        prcs->setStatus("nostatus");
    }
}

void RemoteComputer::whenProcessShouldStart(QString id){
    qDebug() << "[RemoteComputer] Process should start now";
    if(processes.contains(id)){
        RemoteProcess *tmp = processes.value(id);
        QByteArray message = parser.nprMessage(tmp->getId(), tmp->getProgram(), tmp->getParameters());
        communicationHandler.sendData(message);
    }

}

void RemoteComputer::whenProcessShouldStop(QString id){
    if(processes.contains(id)){
        RemoteProcess *tmp = processes.value(id);
        QByteArray message = parser.prgMessage(tmp->getId(), "stop");
        communicationHandler.sendData(message);
    }

}

void RemoteComputer::whenStatusUpdateReceived(QString id, QString status){
    if(processes.contains(id)){
        RemoteProcess *tmp = processes.value(id);
        tmp->setStatus(status);
    }
}

void RemoteComputer::whenCLOReceived(QString id, int type, QString message){
    if(processes.contains(id)){
        RemoteProcess *tmp = processes.value(id);
        tmp->newCloReceived(type, message);
    }
}
